{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# The Very Basics of Musical Instruments Classification using Machine Learning\n",
    "## Short-Time Fourier Transform (STFT) and an Introduction to Convolutional Neural Networks (CNN) using PyTorch\n",
    "\n",
    "<br>\n",
    "\n",
    "<p align=\"left\">\n",
    "<img src=\"./img/businesscard.jpg\" width=\"400px\" alt=\"Business Card\" align=\"left\" >\n",
    "</p>\n",
    "<br>\n",
    "\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Based on the Introduction to Deep Learning for Computer Vision using PyTorch by Kevin McGuinness, DCU\n",
    "https://colab.research.google.com/drive/1gJAAN3UI9005ecVmxPun5ZLCGu4YBtLo"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Environments Configuration"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 1,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "cpu\n",
      "Not inside Google Colab: No module named 'google'. Using standard configurations.\n",
      "processor\t: 0\r\n",
      "vendor_id\t: GenuineIntel\r\n",
      "cpu family\t: 6\r\n",
      "model\t\t: 142\r\n",
      "model name\t: Intel(R) Core(TM) i7-7500U CPU @ 2.70GHz\r\n",
      "stepping\t: 9\r\n",
      "cpu MHz\t\t: 2904.002\r\n",
      "cache size\t: 4096 KB\r\n",
      "physical id\t: 0\r\n",
      "siblings\t: 2\r\n",
      "core id\t\t: 0\r\n",
      "cpu cores\t: 2\r\n",
      "apicid\t\t: 0\r\n",
      "initial apicid\t: 0\r\n",
      "fpu\t\t: yes\r\n",
      "fpu_exception\t: yes\r\n",
      "cpuid level\t: 22\r\n",
      "wp\t\t: yes\r\n",
      "flags\t\t: fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush mmx fxsr sse sse2 ht syscall nx rdtscp lm constant_tsc rep_good nopl xtopology nonstop_tsc cpuid pni pclmulqdq ssse3 cx16 pcid sse4_1 sse4_2 x2apic movbe popcnt aes xsave avx rdrand hypervisor lahf_lm abm 3dnowprefetch invpcid_single pti fsgsbase avx2 invpcid rdseed clflushopt\r\n",
      "bugs\t\t: cpu_meltdown spectre_v1 spectre_v2 spec_store_bypass l1tf\r\n",
      "bogomips\t: 5808.00\r\n",
      "clflush size\t: 64\r\n",
      "cache_alignment\t: 64\r\n",
      "address sizes\t: 39 bits physical, 48 bits virtual\r\n",
      "power management:\r\n",
      "\r\n",
      "processor\t: 1\r\n",
      "vendor_id\t: GenuineIntel\r\n",
      "cpu family\t: 6\r\n",
      "model\t\t: 142\r\n",
      "model name\t: Intel(R) Core(TM) i7-7500U CPU @ 2.70GHz\r\n",
      "stepping\t: 9\r\n",
      "cpu MHz\t\t: 2904.002\r\n",
      "cache size\t: 4096 KB\r\n",
      "physical id\t: 0\r\n",
      "siblings\t: 2\r\n",
      "core id\t\t: 1\r\n",
      "cpu cores\t: 2\r\n",
      "apicid\t\t: 1\r\n",
      "initial apicid\t: 1\r\n",
      "fpu\t\t: yes\r\n",
      "fpu_exception\t: yes\r\n",
      "cpuid level\t: 22\r\n",
      "wp\t\t: yes\r\n",
      "flags\t\t: fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush mmx fxsr sse sse2 ht syscall nx rdtscp lm constant_tsc rep_good nopl xtopology nonstop_tsc cpuid pni pclmulqdq ssse3 cx16 pcid sse4_1 sse4_2 x2apic movbe popcnt aes xsave avx rdrand hypervisor lahf_lm abm 3dnowprefetch invpcid_single pti fsgsbase avx2 invpcid rdseed clflushopt\r\n",
      "bugs\t\t: cpu_meltdown spectre_v1 spectre_v2 spec_store_bypass l1tf\r\n",
      "bogomips\t: 5808.00\r\n",
      "clflush size\t: 64\r\n",
      "cache_alignment\t: 64\r\n",
      "address sizes\t: 39 bits physical, 48 bits virtual\r\n",
      "power management:\r\n",
      "\r\n"
     ]
    }
   ],
   "source": [
    "## Check if inside Google Colab\n",
    "inColab=False\n",
    "## Check CPU or GPU\n",
    "import torch\n",
    "device = torch.device(\"cuda\" if torch.cuda.is_available() else \"cpu\")\n",
    "print(device)\n",
    "\n",
    "try:\n",
    "    import google.colab\n",
    "    from google.colab import widgets\n",
    "    from tensorboardcolab import TensorBoardColab\n",
    "    print(\"Tensorflow Backend only for TensorBoard. Using PyTorch.\")\n",
    "    inColab=True\n",
    "    \n",
    "    # Create Directory for Checkpoints\n",
    "    !mkdir -p checkpoints\n",
    "    \n",
    "    # Install torchaudio\n",
    "    !apt-get update #Update\n",
    "    !apt-get install sox libsox-dev libsox-fmt-all #Install Dependencies\n",
    "    !pip3 install git+git://github.com/pytorch/audio #Install torchaudio\n",
    "    \n",
    "    # Clone Guitars.Ai Basics of Musical Instruments Classification Repository \n",
    "    !git clone https://github.com/GuitarsAI/BasicsMusicalInstrumClassifi\n",
    "    !unzip ./BasicsMusicalInstrumClassifi/audio/*.zip -d ./BasicsMusicalInstrumClassifi/audio\n",
    "    path = \"./BasicsMusicalInstrumClassifi/audio/london_phill_dataset_multi/\"\n",
    "    \n",
    "    # Check for GPU\n",
    "    if device.type == 'cuda':\n",
    "        !nvidia-smi\n",
    "        print(torch.cuda.get_device_name(0))        \n",
    "    else:\n",
    "        print(\"\\nNo GPU Detected. Using CPU. Configure the Runtime for GPU.\\n\".upper())\n",
    "        !cat /proc/cpuinfo\n",
    "    \n",
    "except Exception as e:\n",
    "    if inColab:\n",
    "        print(\"Error in Congiguration.%s\" % e)\n",
    "        stop\n",
    "    \n",
    "    print(\"Not inside Google Colab: %s. Using standard configurations.\" % (e))\n",
    "    # Running in Different Environmet\n",
    "    !cat /proc/cpuinfo\n",
    "    path='./audio/london_phill_dataset_multi/'"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Imports"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/html": [
       "<style>.container { width:80% !important; }</style>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "# Imports\n",
    "\n",
    "#General\n",
    "import numpy as np\n",
    "import itertools\n",
    "\n",
    "# System\n",
    "import os, fnmatch\n",
    "\n",
    "# Visualization\n",
    "import matplotlib.pyplot as plt\n",
    "from IPython.core.display import HTML, display, Image\n",
    "import IPython.display as ipd\n",
    "\n",
    "# Machine Learning\n",
    "from sklearn.preprocessing import LabelEncoder, OneHotEncoder, StandardScaler\n",
    "from sklearn.model_selection import StratifiedShuffleSplit\n",
    "from sklearn.metrics import recall_score, precision_score, accuracy_score\n",
    "from sklearn.metrics import confusion_matrix, f1_score, classification_report\n",
    "\n",
    "# Deep Learning\n",
    "import torch\n",
    "from torch.autograd import Variable\n",
    "import torch.nn.functional as F\n",
    "import torch.nn as nn\n",
    "import torch.optim as optim\n",
    "from torch.utils.data import Dataset, DataLoader\n",
    "\n",
    "# Random Seed\n",
    "from numpy.random import seed\n",
    "seed(0)\n",
    "torch.manual_seed(0)\n",
    "\n",
    "# Audio\n",
    "import librosa.display, librosa\n",
    "from librosa.util import normalize as normalize\n",
    "import torchaudio\n",
    "import torchaudio.transforms as transforms\n",
    "\n",
    "# Configure Jupyter Cell Size\n",
    "display(HTML(\"<style>.container { width:80% !important; }</style>\"))"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Parameters"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Signal Processing Parameters\n",
    "fs = 44100         # Sampling Frequency\n",
    "n_fft = 2048       # Length of the FFT \n",
    "hop_length = 512   # Number of samples in frames\n",
    "duration = 1       # Duration of audio 1s\n",
    "\n",
    "# Machine Learning Parameters\n",
    "testset_size = 0.25   # Percentage of data for Testing\n",
    "batch_size = 1        # How may samples per batch to load\n",
    "num_epochs = 15       # Number of Epochs\n",
    "lr = 0.01             # Learning Rate\n",
    "    "
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Get Audio Files and Generate Labels"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Get viola_Gs4_025_pianissimo_arco-normal.mp3\n",
      "Get viola_A4_1_fortissimo_snap-pizz.mp3\n",
      "Get viola_A3_1_piano_pizz-normal.mp3\n",
      "Get viola_Gs4_05_pianissimo_arco-normal.mp3\n",
      "Get viola_Gs3_025_fortissimo_arco-normal.mp3\n",
      "Get viola_A3_1_piano_arco-normal.mp3\n",
      "Get viola_A4_025_piano_arco-normal.mp3\n",
      "Get viola_A3_025_mezzo-piano_arco-normal.mp3\n",
      "Get viola_Gs4_15_mezzo-piano_arco-normal.mp3\n",
      "Get viola_A5_1_fortissimo_arco-normal.mp3\n",
      "Get viola_Gs4_1_mezzo-piano_arco-normal.mp3\n",
      "Get viola_Gs5_05_fortissimo_arco-normal.mp3\n",
      "Get viola_Gs5_1_fortissimo_snap-pizz.mp3\n",
      "Get viola_Gs5_025_mezzo-piano_arco-normal.mp3\n",
      "Get viola_A3_1_fortissimo_arco-normal.mp3\n",
      "Get viola_A4_15_fortissimo_arco-normal.mp3\n",
      "Get viola_A4_05_forte_arco-normal.mp3\n",
      "Get viola_A5_1_pianissimo_arco-normal.mp3\n",
      "Get viola_A4_1_piano_arco-normal.mp3\n",
      "Get viola_A3_025_fortissimo_arco-normal.mp3\n",
      "Get viola_Gs6_025_pianissimo_arco-normal.mp3\n",
      "Get viola_Gs6_05_fortissimo_arco-normal.mp3\n",
      "Get viola_Gs6_05_pianissimo_arco-normal.mp3\n",
      "Get viola_Gs4_025_mezzo-piano_arco-normal.mp3\n",
      "Get viola_Gs5_1_fortissimo_arco-normal.mp3\n",
      "Get viola_A3_1_forte_arco-normal.mp3\n",
      "Get viola_Gs3_15_fortissimo_arco-normal.mp3\n",
      "Get viola_Gs4_025_fortissimo_arco-normal.mp3\n",
      "Get viola_Gs6_05_piano_arco-normal.mp3\n",
      "Get viola_Gs4_15_pianissimo_arco-normal.mp3\n",
      "Get viola_A4_05_fortissimo_arco-normal.mp3\n",
      "Get viola_A5_1_mezzo-forte_artificial-harmonic.mp3\n",
      "Get viola_Gs5_05_piano_arco-normal.mp3\n",
      "Get viola_A4_1_mezzo-forte_arco-major-trill.mp3\n",
      "Get viola_Gs3_025_piano_arco-normal.mp3\n",
      "Get viola_Gs4_1_piano_arco-normal.mp3\n",
      "Get viola_Gs5_15_fortissimo_arco-normal.mp3\n",
      "Get viola_A4_05_pianissimo_arco-normal.mp3\n",
      "Get viola_A4_05_piano_arco-normal.mp3\n",
      "Get viola_Ds3_1_piano_pizz-normal.mp3\n",
      "Get viola_A3_1_pianissimo_arco-normal.mp3\n",
      "Get viola_A3_15_fortissimo_arco-normal.mp3\n",
      "Get viola_A5_1_forte_arco-normal.mp3\n",
      "Get viola_Gs3_025_mezzo-piano_arco-normal.mp3\n",
      "Get viola_Gs5_15_pianissimo_arco-normal.mp3\n",
      "Get viola_A3_05_fortissimo_arco-normal.mp3\n",
      "Get viola_Ds3_05_mezzo-piano_arco-normal.mp3\n",
      "Get viola_Gs6_1_pianissimo_arco-normal.mp3\n",
      "Get viola_Gs3_15_pianissimo_arco-normal.mp3\n",
      "Get viola_A3_1_mezzo-forte_molto-vibrato.mp3\n",
      "Get viola_Gs6_025_fortissimo_arco-normal.mp3\n",
      "Get viola_A3_1_fortissimo_pizz-normal.mp3\n",
      "Get viola_Gs6_1_fortissimo_arco-normal.mp3\n",
      "Get viola_A3_15_piano_arco-normal.mp3\n",
      "Get viola_A4_1_mezzo-forte_arco-minor-trill.mp3\n",
      "Get viola_A4_1_fortissimo_arco-normal.mp3\n",
      "Get viola_A3_025_piano_arco-normal.mp3\n",
      "Get viola_A3_05_pianissimo_arco-normal.mp3\n",
      "Get viola_A4_1_piano_pizz-normal.mp3\n",
      "Get viola_A3_1_piano_arco-glissando.mp3\n",
      "Get viola_A4_1_pianissimo_arco-normal.mp3\n",
      "Get viola_Gs6_1_forte_arco-normal.mp3\n",
      "Get viola_Gs5_05_forte_arco-normal.mp3\n",
      "Get viola_A4_1_forte_arco-normal.mp3\n",
      "Get viola_A3_05_piano_arco-normal.mp3\n",
      "Get viola_Gs5_05_pianissimo_arco-normal.mp3\n",
      "Get viola_Gs4_1_fortissimo_arco-normal.mp3\n",
      "Get viola_Gs5_025_fortissimo_arco-normal.mp3\n",
      "Get viola_Gs5_025_pianissimo_arco-normal.mp3\n",
      "Get viola_Gs5_1_piano_arco-normal.mp3\n",
      "Get viola_Gs3_025_pianissimo_arco-normal.mp3\n",
      "Get viola_Gs4_1_pianissimo_arco-normal.mp3\n",
      "Get viola_A4_1_mezzo-piano_non-vibrato.mp3\n",
      "Get viola_Gs4_05_mezzo-piano_arco-normal.mp3\n",
      "Get viola_A4_025_mezzo-piano_arco-normal.mp3\n",
      "Get viola_A4_025_pianissimo_arco-normal.mp3\n",
      "Get viola_A4_15_piano_arco-normal.mp3\n",
      "Get viola_Gs6_05_forte_arco-normal.mp3\n",
      "Get viola_Gs6_15_fortissimo_arco-normal.mp3\n",
      "Get viola_Gs6_025_forte_arco-normal.mp3\n",
      "Get viola_A4_15_pianissimo_arco-normal.mp3\n",
      "Get viola_Gs3_15_piano_arco-normal.mp3\n",
      "Get viola_A3_05_mezzo-piano_arco-normal.mp3\n",
      "Get viola_Gs6_025_mezzo-piano_arco-normal.mp3\n",
      "Get viola_Gs6_15_forte_arco-normal.mp3\n",
      "Get viola_Gs4_15_fortissimo_arco-normal.mp3\n",
      "Get viola_A4_025_fortissimo_arco-normal.mp3\n",
      "Get viola_Ds3_05_fortissimo_arco-normal.mp3\n",
      "Get viola_A4_05_mezzo-piano_arco-normal.mp3\n",
      "Get viola_Gs5_1_pianissimo_arco-normal.mp3\n",
      "Get viola_Gs4_05_fortissimo_arco-normal.mp3\n",
      "Get viola_Gs6_025_piano_arco-normal.mp3\n",
      "Get viola_A4_1_mezzo-forte_molto-vibrato.mp3\n",
      "Get viola_A3_15_forte_arco-normal.mp3\n",
      "Get viola_Gs5_025_forte_arco-normal.mp3\n",
      "Get viola_A3_025_pianissimo_arco-normal.mp3\n",
      "Get viola_Gs4_05_piano_arco-normal.mp3\n",
      "Get viola_A3_1_mezzo-piano_non-vibrato.mp3\n",
      "Get viola_A4_1_piano_arco-glissando.mp3\n",
      "Get viola_Gs5_1_forte_arco-normal.mp3\n",
      "Get saxophone_A4_1_piano_normal.mp3\n",
      "Get saxophone_A4_1_mezzo-forte_normal.mp3\n",
      "Get saxophone_A3_1_piano_normal.mp3\n",
      "Get saxophone_A3_1_fortissimo_normal.mp3\n",
      "Get saxophone_Gs4_025_fortissimo_normal.mp3\n",
      "Get saxophone_A5_05_fortissimo_normal.mp3\n",
      "Get saxophone_Gs3_05_fortissimo_normal.mp3\n",
      "Get saxophone_A3_05_pianissimo_normal.mp3\n",
      "Get saxophone_Gs4_15_forte_normal.mp3\n",
      "Get saxophone_Ds4_05_pianissimo_normal.mp3\n",
      "Get saxophone_A4_05_fortissimo_normal.mp3\n",
      "Get saxophone_Gs3_025_fortissimo_normal.mp3\n",
      "Get saxophone_Gs4_05_piano_normal.mp3\n",
      "Get saxophone_A5_1_forte_normal.mp3\n",
      "Get saxophone_A3_025_fortissimo_normal.mp3\n",
      "Get saxophone_A3_15_fortissimo_normal.mp3\n",
      "Get saxophone_Gs3_05_mezzo-piano_normal.mp3\n",
      "Get saxophone_Ds4_025_fortissimo_normal.mp3\n",
      "Get saxophone_Ds4_05_piano_normal.mp3\n",
      "Get saxophone_A3_025_mezzo-piano_normal.mp3\n",
      "Get saxophone_Gs3_05_piano_normal.mp3\n",
      "Get saxophone_Ds4_025_forte_normal.mp3\n",
      "Get saxophone_A4_15_forte_normal.mp3\n",
      "Get saxophone_Gs5_15_pianissimo_normal.mp3\n",
      "Get saxophone_Gs4_1_pianissimo_normal.mp3\n",
      "Get saxophone_Ds5_1_forte_major-trill.mp3\n",
      "Get saxophone_A3_025_pianissimo_normal.mp3\n",
      "Get saxophone_Gs4_025_forte_normal.mp3\n",
      "Get saxophone_Ds4_15_fortissimo_normal.mp3\n",
      "Get saxophone_Ds4_025_mezzo-forte_normal.mp3\n",
      "Get saxophone_A5_05_forte_normal.mp3\n",
      "Get saxophone_Gs5_15_fortissimo_normal.mp3\n",
      "Get saxophone_Gs3_025_forte_normal.mp3\n",
      "Get saxophone_Gs5_05_pianissimo_normal.mp3\n",
      "Get saxophone_A5_1_pianissimo_normal.mp3\n",
      "Get saxophone_Gs5_05_forte_normal.mp3\n",
      "Get saxophone_Gs4_025_pianissimo_normal.mp3\n",
      "Get saxophone_Gs5_025_forte_normal.mp3\n",
      "Get saxophone_Gs3_1_piano_normal.mp3\n",
      "Get saxophone_Gs4_05_mezzo-forte_normal.mp3\n",
      "Get saxophone_A5_15_pianissimo_normal.mp3\n",
      "Get saxophone_Gs5_1_forte_normal.mp3\n",
      "Get saxophone_Gs4_1_forte_normal.mp3\n",
      "Get saxophone_Gs5_1_fortissimo_normal.mp3\n",
      "Get saxophone_Gs4_025_piano_normal.mp3\n",
      "Get saxophone_Gs4_1_piano_normal.mp3\n",
      "Get saxophone_Gs5_025_fortissimo_normal.mp3\n",
      "Get saxophone_Gs3_1_pianissimo_normal.mp3\n",
      "Get saxophone_Gs4_05_fortissimo_normal.mp3\n",
      "Get saxophone_A4_05_forte_normal.mp3\n",
      "Get saxophone_Gs3_05_pianissimo_normal.mp3\n",
      "Get saxophone_Gs5_15_piano_normal.mp3\n",
      "Get saxophone_A4_025_fortissimo_normal.mp3\n",
      "Get saxophone_A5_1_piano_normal.mp3\n",
      "Get saxophone_Gs5_025_piano_normal.mp3\n",
      "Get saxophone_Gs5_05_fortissimo_normal.mp3\n",
      "Get saxophone_A5_15_forte_normal.mp3\n",
      "Get saxophone_Gs4_05_forte_normal.mp3\n",
      "Get saxophone_Gs5_05_piano_normal.mp3\n",
      "Get saxophone_Gs5_1_piano_normal.mp3\n",
      "Get saxophone_A5_05_piano_normal.mp3\n",
      "Get saxophone_A3_15_pianissimo_normal.mp3\n",
      "Get saxophone_A5_15_fortissimo_normal.mp3\n",
      "Get saxophone_Gs5_1_pianissimo_normal.mp3\n",
      "Get saxophone_Gs4_15_pianissimo_normal.mp3\n",
      "Get saxophone_Ds4_05_pianissimo_subtone.mp3\n",
      "Get saxophone_A5_05_pianissimo_normal.mp3\n",
      "Get saxophone_Ds4_025_pianissimo_normal.mp3\n",
      "Get saxophone_A3_05_fortissimo_normal.mp3\n",
      "Get saxophone_Gs4_15_fortissimo_normal.mp3\n",
      "Get saxophone_A4_05_piano_normal.mp3\n",
      "Get saxophone_A4_15_piano_normal.mp3\n",
      "Get saxophone_Ds4_05_mezzo-forte_normal.mp3\n",
      "Get saxophone_A3_025_forte_normal.mp3\n",
      "Get saxophone_Gs3_05_forte_normal.mp3\n",
      "Get saxophone_A3_1_pianissimo_normal.mp3\n",
      "Get saxophone_A4_025_piano_normal.mp3\n",
      "Get saxophone_A4_1_pianissimo_normal.mp3\n",
      "Get saxophone_A4_1_forte_normal.mp3\n",
      "Get saxophone_Gs3_15_fortissimo_normal.mp3\n",
      "Get saxophone_Ds4_05_mezzo-forte_slap-tongue.mp3\n",
      "Get saxophone_Gs4_1_fortissimo_normal.mp3\n",
      "Get saxophone_Gs5_15_forte_normal.mp3\n",
      "Get saxophone_A4_1_fortissimo_normal.mp3\n",
      "Get saxophone_A4_05_pianissimo_normal.mp3\n",
      "Get saxophone_Ds4_05_fortissimo_normal.mp3\n",
      "Get saxophone_Gs4_15_piano_normal.mp3\n",
      "Get saxophone_Gs3_15_pianissimo_normal.mp3\n",
      "Get saxophone_Ds5_1_forte_minor-trill.mp3\n",
      "Get saxophone_A3_1_forte_normal.mp3\n",
      "Get saxophone_A3_05_piano_normal.mp3\n",
      "Get saxophone_A3_05_forte_normal.mp3\n",
      "Get saxophone_A5_1_fortissimo_normal.mp3\n",
      "Get saxophone_A4_025_forte_normal.mp3\n",
      "Get saxophone_A3_05_mezzo-piano_normal.mp3\n",
      "Get saxophone_A4_15_fortissimo_normal.mp3\n",
      "Get saxophone_Gs3_025_mezzo-piano_normal.mp3\n",
      "Get saxophone_Gs4_025_mezzo-forte_normal.mp3\n",
      "Get saxophone_A3_15_forte_normal.mp3\n",
      "Get saxophone_Gs4_05_pianissimo_normal.mp3\n",
      "Get oboe_Gs6_025_forte_normal.mp3\n",
      "Get oboe_Gs5_05_fortissimo_normal.mp3\n",
      "Get oboe_Gs5_05_forte_normal.mp3\n",
      "Get oboe_A4_025_fortissimo_normal.mp3\n",
      "Get oboe_A5_025_fortissimo_normal.mp3\n",
      "Get oboe_A5_15_forte_normal.mp3\n",
      "Get oboe_Gs5_15_forte_normal.mp3\n",
      "Get oboe_A5_15_fortissimo_normal.mp3\n",
      "Get oboe_Gs6_025_piano_normal.mp3\n",
      "Get oboe_A5_1_forte_minor-trill.mp3\n",
      "Get oboe_Gs6_1_piano_normal.mp3\n",
      "Get oboe_Gs4_025_piano_normal.mp3\n",
      "Get oboe_A4_1_fortissimo_normal.mp3\n",
      "Get oboe_Gs5_1_piano_normal.mp3\n",
      "Get oboe_Gs4_05_fortissimo_normal.mp3\n",
      "Get oboe_A4_15_piano_normal.mp3\n",
      "Get oboe_Gs4_025_forte_normal.mp3\n",
      "Get oboe_Gs6_15_piano_normal.mp3\n",
      "Get oboe_A6_05_piano_normal.mp3\n",
      "Get oboe_Gs6_1_mezzo-forte_normal.mp3\n",
      "Get oboe_Gs6_05_piano_normal.mp3\n",
      "Get oboe_Gs5_15_mezzo-forte_normal.mp3\n",
      "Get oboe_A4_025_forte_normal.mp3\n",
      "Get oboe_A5_05_fortissimo_normal.mp3\n",
      "Get oboe_As3_1_piano_normal.mp3\n",
      "Get oboe_A6_15_piano_normal.mp3\n",
      "Get oboe_A6_025_piano_normal.mp3\n",
      "Get oboe_As3_05_fortissimo_normal.mp3\n",
      "Get oboe_G6_025_forte_normal.mp3\n",
      "Get oboe_A5_05_piano_normal.mp3\n",
      "Get oboe_A4_05_piano_normal.mp3\n",
      "Get oboe_Gs5_025_forte_normal.mp3\n",
      "Get oboe_Ds6_15_forte_normal.mp3\n",
      "Get oboe_A5_05_forte_normal.mp3\n",
      "Get oboe_A5_025_piano_normal.mp3\n",
      "Get oboe_Gs4_15_fortissimo_normal.mp3\n",
      "Get oboe_Gs5_15_fortissimo_normal.mp3\n",
      "Get oboe_A5_025_forte_normal.mp3\n",
      "Get oboe_Gs6_05_forte_normal.mp3\n",
      "Get oboe_G6_025_piano_normal.mp3\n",
      "Get oboe_Gs5_15_piano_normal.mp3\n",
      "Get oboe_A6_1_piano_normal.mp3\n",
      "Get oboe_A4_15_forte_normal.mp3\n",
      "Get oboe_Gs5_1_mezzo-forte_normal.mp3\n",
      "Get oboe_As3_1_mezzo-forte_normal.mp3\n",
      "Get oboe_Gs4_15_mezzo-forte_normal.mp3\n",
      "Get oboe_Gs4_025_fortissimo_normal.mp3\n",
      "Get oboe_A5_15_mezzo-forte_normal.mp3\n",
      "Get oboe_Gs6_025_mezzo-forte_normal.mp3\n",
      "Get oboe_Ds6_05_mezzo-forte_normal.mp3\n",
      "Get oboe_Gs4_1_fortissimo_normal.mp3\n",
      "Get oboe_As3_05_mezzo-forte_normal.mp3\n",
      "Get oboe_Gs5_025_mezzo-forte_normal.mp3\n",
      "Get oboe_Ds6_05_fortissimo_normal.mp3\n",
      "Get oboe_Gs6_15_forte_normal.mp3\n",
      "Get oboe_Gs4_1_forte_normal.mp3\n",
      "Get oboe_A4_1_forte_normal.mp3\n",
      "Get oboe_Gs6_05_mezzo-forte_normal.mp3\n",
      "Get oboe_As3_15_mezzo-forte_normal.mp3\n",
      "Get oboe_Gs4_05_forte_normal.mp3\n",
      "Get oboe_A5_1_forte_major-trill.mp3\n",
      "Get oboe_A4_05_fortissimo_normal.mp3\n",
      "Get oboe_Gs5_05_piano_normal.mp3\n",
      "Get oboe_A5_15_piano_normal.mp3\n",
      "Get oboe_A6_1_forte_minor-trill.mp3\n",
      "Get oboe_Gs4_05_mezzo-forte_normal.mp3\n",
      "Get oboe_Gs4_1_forte_minor-trill.mp3\n",
      "Get oboe_Gs5_1_forte_normal.mp3\n",
      "Get oboe_Gs5_025_fortissimo_normal.mp3\n",
      "Get oboe_Gs5_025_piano_normal.mp3\n",
      "Get oboe_A5_025_mezzo-forte_normal.mp3\n",
      "Get oboe_Gs5_1_fortissimo_normal.mp3\n",
      "Get oboe_A4_05_forte_normal.mp3\n",
      "Get oboe_Gs5_05_mezzo-forte_normal.mp3\n",
      "Get oboe_A5_1_fortissimo_normal.mp3\n",
      "Get oboe_Gs6_15_mezzo-forte_normal.mp3\n",
      "Get oboe_A6_1_forte_major-trill.mp3\n",
      "Get oboe_As3_05_forte_normal.mp3\n",
      "Get oboe_As3_1_forte_normal.mp3\n",
      "Get oboe_Gs6_1_forte_normal.mp3\n",
      "Get oboe_Gs4_1_piano_normal.mp3\n",
      "Get oboe_As3_15_forte_normal.mp3\n",
      "Get oboe_As3_05_piano_normal.mp3\n",
      "Get oboe_A5_1_mezzo-forte_normal.mp3\n",
      "Get oboe_A4_1_piano_normal.mp3\n",
      "Get oboe_Gs4_15_forte_normal.mp3\n",
      "Get oboe_Gs4_05_piano_normal.mp3\n",
      "Get oboe_Gs4_1_forte_major-trill.mp3\n",
      "Get oboe_A4_1_mezzo-forte_normal.mp3\n",
      "Get oboe_A4_025_piano_normal.mp3\n",
      "Get oboe_A5_05_mezzo-forte_normal.mp3\n",
      "Get oboe_A5_1_piano_normal.mp3\n",
      "Get oboe_Gs4_15_piano_normal.mp3\n",
      "Get oboe_As3_15_fortissimo_normal.mp3\n",
      "Get oboe_Gs4_1_mezzo-forte_normal.mp3\n",
      "Get oboe_As3_1_fortissimo_normal.mp3\n",
      "Get oboe_A5_1_forte_normal.mp3\n",
      "Get oboe_G6_025_mezzo-forte_normal.mp3\n",
      "Get oboe_Gs4_025_mezzo-forte_normal.mp3\n",
      "Get oboe_Ds6_05_piano_normal.mp3\n",
      "Get trumpet_B3_025_forte_normal.mp3\n",
      "Get trumpet_Cs4_05_pianissimo_normal.mp3\n",
      "Get trumpet_G3_025_pianissimo_normal.mp3\n",
      "Get trumpet_Gs5_05_mezzo-forte_normal.mp3\n",
      "Get trumpet_E6_1_forte_normal.mp3\n",
      "Get trumpet_Ds4_15_pianissimo_normal.mp3\n",
      "Get trumpet_A3_05_pianissimo_normal.mp3\n",
      "Get trumpet_Ds4_025_pianissimo_normal.mp3\n",
      "Get trumpet_B3_05_forte_normal.mp3\n",
      "Get trumpet_C4_15_pianissimo_normal.mp3\n",
      "Get trumpet_Ds4_05_pianissimo_normal.mp3\n",
      "Get trumpet_F3_05_pianissimo_normal.mp3\n",
      "Get trumpet_As3_1_pianissimo_normal.mp3\n",
      "Get trumpet_D6_05_forte_normal.mp3\n",
      "Get trumpet_Cs6_025_forte_normal.mp3\n",
      "Get trumpet_A3_05_forte_normal.mp3\n",
      "Get trumpet_E4_025_pianissimo_normal.mp3\n",
      "Get trumpet_As3_05_pianissimo_normal.mp3\n",
      "Get trumpet_E3_05_forte_normal.mp3\n",
      "Get trumpet_G5_1_mezzo-forte_normal.mp3\n",
      "Get trumpet_G5_025_mezzo-forte_normal.mp3\n",
      "Get trumpet_B5_025_mezzo-forte_normal.mp3\n",
      "Get trumpet_F3_025_forte_normal.mp3\n",
      "Get trumpet_D4_15_pianissimo_normal.mp3\n",
      "Get trumpet_E4_15_pianissimo_normal.mp3\n",
      "Get trumpet_Cs4_15_pianissimo_normal.mp3\n",
      "Get trumpet_D4_05_pianissimo_normal.mp3\n",
      "Get trumpet_E6_025_forte_normal.mp3\n",
      "Get trumpet_Ds6_025_forte_normal.mp3\n",
      "Get trumpet_E3_025_pianissimo_normal.mp3\n",
      "Get trumpet_B5_025_forte_normal.mp3\n",
      "Get trumpet_C6_025_forte_normal.mp3\n",
      "Get trumpet_D4_05_forte_normal.mp3\n",
      "Get trumpet_As4_025_forte_normal.mp3\n",
      "Get trumpet_F4_025_pianissimo_normal.mp3\n",
      "Get trumpet_A3_15_pianissimo_normal.mp3\n",
      "Get trumpet_Gs3_1_pianissimo_normal.mp3\n",
      "Get trumpet_Gs3_05_pianissimo_normal.mp3\n",
      "Get trumpet_F4_05_pianissimo_normal.mp3\n",
      "Get trumpet_D4_025_forte_normal.mp3\n",
      "Get trumpet_Cs4_1_pianissimo_normal.mp3\n",
      "Get trumpet_C4_025_forte_normal.mp3\n",
      "Get trumpet_C4_1_pianissimo_normal.mp3\n",
      "Get trumpet_A4_05_forte_normal.mp3\n",
      "Get trumpet_G3_15_pianissimo_normal.mp3\n",
      "Get trumpet_Cs4_05_forte_normal.mp3\n",
      "Get trumpet_Gs3_15_pianissimo_normal.mp3\n",
      "Get trumpet_B3_1_pianissimo_normal.mp3\n",
      "Get trumpet_As5_05_forte_normal.mp3\n",
      "Get trumpet_Ds4_1_pianissimo_normal.mp3\n",
      "Get trumpet_Gs3_025_pianissimo_normal.mp3\n",
      "Get trumpet_C4_05_pianissimo_normal.mp3\n",
      "Get trumpet_Ds4_05_forte_normal.mp3\n",
      "Get trumpet_E3_15_pianissimo_normal.mp3\n",
      "Get trumpet_Gs3_05_forte_normal.mp3\n",
      "Get trumpet_As3_15_pianissimo_normal.mp3\n",
      "Get trumpet_B4_025_forte_normal.mp3\n",
      "Get trumpet_As5_05_mezzo-forte_normal.mp3\n",
      "Get trumpet_E4_1_pianissimo_normal.mp3\n",
      "Get trumpet_F3_05_forte_normal.mp3\n",
      "Get trumpet_Gs3_1_forte_normal.mp3\n",
      "Get trumpet_Ds6_05_forte_normal.mp3\n",
      "Get trumpet_D6_025_forte_normal.mp3\n",
      "Get trumpet_Gs5_05_forte_normal.mp3\n",
      "Get trumpet_Gs5_025_forte_normal.mp3\n",
      "Get trumpet_B3_05_pianissimo_normal.mp3\n",
      "Get trumpet_A5_025_mezzo-forte_normal.mp3\n",
      "Get trumpet_Gs4_025_forte_normal.mp3\n",
      "Get trumpet_A4_025_forte_normal.mp3\n",
      "Get trumpet_D4_025_pianissimo_normal.mp3\n",
      "Get trumpet_E4_05_pianissimo_normal.mp3\n",
      "Get trumpet_F3_15_pianissimo_normal.mp3\n",
      "Get trumpet_D5_05_forte_normal.mp3\n",
      "Get trumpet_Ds5_05_forte_normal.mp3\n",
      "Get trumpet_As5_025_forte_normal.mp3\n",
      "Get trumpet_A3_1_pianissimo_normal.mp3\n",
      "Get trumpet_As3_025_forte_normal.mp3\n",
      "Get trumpet_G3_05_pianissimo_normal.mp3\n",
      "Get trumpet_C6_05_forte_normal.mp3\n",
      "Get trumpet_A3_025_pianissimo_normal.mp3\n",
      "Get trumpet_C4_025_pianissimo_normal.mp3\n",
      "Get trumpet_F3_1_forte_normal.mp3\n",
      "Get trumpet_B3_15_pianissimo_normal.mp3\n",
      "Get trumpet_G5_15_mezzo-forte_normal.mp3\n",
      "Get trumpet_A5_025_forte_normal.mp3\n",
      "Get trumpet_Cs4_025_pianissimo_normal.mp3\n",
      "Get trumpet_As3_025_pianissimo_normal.mp3\n",
      "Get trumpet_F3_1_pianissimo_normal.mp3\n",
      "Get trumpet_D4_1_pianissimo_normal.mp3\n",
      "Get trumpet_Gs5_025_mezzo-forte_normal.mp3\n",
      "Get trumpet_G3_1_pianissimo_normal.mp3\n",
      "Get trumpet_E3_05_pianissimo_normal.mp3\n",
      "Get trumpet_A5_05_mezzo-forte_normal.mp3\n",
      "Get trumpet_G5_05_mezzo-forte_normal.mp3\n",
      "Get trumpet_C4_05_forte_normal.mp3\n",
      "Get trumpet_E3_1_pianissimo_normal.mp3\n",
      "Get trumpet_B3_025_pianissimo_normal.mp3\n",
      "Get trumpet_F3_025_pianissimo_normal.mp3\n",
      "Get trumpet_Gs4_05_forte_normal.mp3\n",
      "Get trumpet_E3_1_forte_normal.mp3\n",
      "Get flute_Gs5_1_piano_normal.mp3\n",
      "Get flute_A5_1_piano_normal.mp3\n",
      "Get flute_Gs4_025_mezzo-piano_normal.mp3\n",
      "Get flute_A6_05_pianissimo_normal.mp3\n",
      "Get flute_A5_025_pianissimo_normal.mp3\n",
      "Get flute_A4_15_mezzo-piano_normal.mp3\n",
      "Get flute_A5_05_forte_normal.mp3\n",
      "Get flute_Gs5_15_mezzo-forte_normal.mp3\n",
      "Get flute_Gs5_1_mezzo-forte_normal.mp3\n",
      "Get flute_A5_05_mezzo-piano_normal.mp3\n",
      "Get flute_Gs5_025_mezzo-piano_normal.mp3\n",
      "Get flute_Gs4_05_pianissimo_normal.mp3\n",
      "Get flute_Gs5_15_piano_normal.mp3\n",
      "Get flute_Gs6_1_mezzo-forte_normal.mp3\n",
      "Get flute_Gs6_15_piano_normal.mp3\n",
      "Get flute_Gs5_025_piano_normal.mp3\n",
      "Get flute_A4_025_mezzo-piano_normal.mp3\n",
      "Get flute_A4_05_mezzo-forte_normal.mp3\n",
      "Get flute_Gs6_025_piano_normal.mp3\n",
      "Get flute_Gs4_15_mezzo-forte_normal.mp3\n",
      "Get flute_Gs6_1_forte_normal.mp3\n",
      "Get flute_A6_05_piano_normal.mp3\n",
      "Get flute_Gs4_15_mezzo-piano_normal.mp3\n",
      "Get flute_A5_15_forte_normal.mp3\n",
      "Get flute_A4_025_piano_normal.mp3\n",
      "Get flute_A4_1_mezzo-forte_normal.mp3\n",
      "Get flute_Gs6_15_mezzo-forte_normal.mp3\n",
      "Get flute_A6_15_forte_normal.mp3\n",
      "Get flute_Gs4_025_pianissimo_normal.mp3\n",
      "Get flute_A5_025_forte_normal.mp3\n",
      "Get flute_A5_05_pianissimo_normal.mp3\n",
      "Get flute_Gs5_05_piano_normal.mp3\n",
      "Get flute_A6_1_fortissimo_minor-trill.mp3\n",
      "Get flute_Gs4_05_forte_normal.mp3\n",
      "Get flute_Gs6_1_pianissimo_normal.mp3\n",
      "Get flute_Gs6_025_pianissimo_normal.mp3\n",
      "Get flute_A4_05_mezzo-piano_normal.mp3\n",
      "Get flute_A5_025_piano_normal.mp3\n",
      "Get flute_A6_1_forte_normal.mp3\n",
      "Get flute_Gs4_05_mezzo-forte_normal.mp3\n",
      "Get flute_Gs4_025_forte_normal.mp3\n",
      "Get flute_A5_1_pianissimo_normal.mp3\n",
      "Get flute_A6_1_mezzo-forte_normal.mp3\n",
      "Get flute_Gs4_15_piano_normal.mp3\n",
      "Get flute_Gs5_05_forte_normal.mp3\n",
      "Get flute_Gs5_05_mezzo-forte_normal.mp3\n",
      "Get flute_Gs6_15_forte_normal.mp3\n",
      "Get flute_A4_15_forte_normal.mp3\n",
      "Get flute_A5_15_pianissimo_normal.mp3\n",
      "Get flute_Gs5_15_mezzo-piano_normal.mp3\n",
      "Get flute_A4_15_pianissimo_normal.mp3\n",
      "Get flute_A6_05_forte_normal.mp3\n",
      "Get flute_A4_15_piano_normal.mp3\n",
      "Get flute_A5_15_mezzo-forte_normal.mp3\n",
      "Get flute_A4_1_mezzo-piano_normal.mp3\n",
      "Get flute_A5_15_mezzo-piano_normal.mp3\n",
      "Get flute_A5_1_forte_normal.mp3\n",
      "Get flute_Gs5_1_mezzo-piano_normal.mp3\n",
      "Get flute_Gs5_025_mezzo-forte_normal.mp3\n",
      "Get flute_Gs5_025_pianissimo_normal.mp3\n",
      "Get flute_Gs6_05_mezzo-forte_normal.mp3\n",
      "Get flute_A4_025_pianissimo_normal.mp3\n",
      "Get flute_Gs5_15_forte_normal.mp3\n",
      "Get flute_A5_1_mezzo-forte_normal.mp3\n",
      "Get flute_Gs6_05_piano_normal.mp3\n",
      "Get flute_A4_05_forte_normal.mp3\n",
      "Get flute_A5_15_piano_normal.mp3\n",
      "Get flute_A4_15_mezzo-forte_normal.mp3\n",
      "Get flute_Gs6_025_forte_normal.mp3\n",
      "Get flute_A4_05_pianissimo_normal.mp3\n",
      "Get flute_Gs6_15_pianissimo_normal.mp3\n",
      "Get flute_Gs4_025_piano_normal.mp3\n",
      "Get flute_Gs4_05_mezzo-piano_normal.mp3\n",
      "Get flute_Gs4_025_mezzo-forte_normal.mp3\n",
      "Get flute_Gs6_05_pianissimo_normal.mp3\n",
      "Get flute_A6_1_piano_normal.mp3\n",
      "Get flute_Gs4_15_forte_normal.mp3\n",
      "Get flute_A5_025_mezzo-piano_normal.mp3\n",
      "Get flute_A5_05_piano_normal.mp3\n",
      "Get flute_Gs6_025_mezzo-forte_normal.mp3\n",
      "Get flute_Gs4_05_piano_normal.mp3\n",
      "Get flute_Gs5_1_pianissimo_normal.mp3\n",
      "Get flute_Gs6_1_piano_normal.mp3\n",
      "Get flute_Gs5_05_pianissimo_normal.mp3\n",
      "Get flute_A4_025_forte_normal.mp3\n",
      "Get flute_A4_1_pianissimo_normal.mp3\n",
      "Get flute_A6_1_pianissimo_normal.mp3\n",
      "Get flute_A4_1_forte_normal.mp3\n",
      "Get flute_A5_1_mezzo-piano_normal.mp3\n",
      "Get flute_A4_025_mezzo-forte_normal.mp3\n",
      "Get flute_Gs6_05_forte_normal.mp3\n",
      "Get flute_A5_025_mezzo-forte_normal.mp3\n",
      "Get flute_A4_1_piano_normal.mp3\n",
      "Get flute_A5_05_mezzo-forte_normal.mp3\n",
      "Get flute_A6_05_mezzo-forte_normal.mp3\n",
      "Get flute_Gs5_05_mezzo-piano_normal.mp3\n",
      "Get flute_Gs5_1_forte_normal.mp3\n",
      "Get flute_A4_05_piano_normal.mp3\n",
      "Get flute_Gs5_025_forte_normal.mp3\n",
      "Get flute_Gs4_15_pianissimo_normal.mp3\n",
      "Get cello_Gs5_025_mezzo-piano_arco-normal.mp3\n",
      "Get cello_Gs5_15_forte_arco-normal.mp3\n",
      "Get cello_A2_05_pianissimo_arco-normal.mp3\n",
      "Get cello_Gs4_05_pianissimo_arco-normal.mp3\n",
      "Get cello_A2_1_fortissimo_arco-normal.mp3\n",
      "Get cello_A3_025_pianissimo_arco-normal.mp3\n",
      "Get cello_Gs5_05_forte_arco-normal.mp3\n",
      "Get cello_A3_1_mezzo-piano_non-vibrato.mp3\n",
      "Get cello_A2_1_forte_arco-normal.mp3\n",
      "Get cello_Gs4_15_pianissimo_arco-normal.mp3\n",
      "Get cello_Gs4_025_forte_arco-normal.mp3\n",
      "Get cello_A3_05_fortissimo_arco-normal.mp3\n",
      "Get cello_Gs5_05_fortissimo_arco-normal.mp3\n",
      "Get cello_A3_1_pianissimo_arco-normal.mp3\n",
      "Get cello_A3_05_forte_arco-normal.mp3\n",
      "Get cello_Gs3_1_forte_arco-normal.mp3\n",
      "Get cello_A4_05_mezzo-piano_arco-normal.mp3\n",
      "Get cello_Gs3_1_mezzo-piano_arco-normal.mp3\n",
      "Get cello_Gs3_025_mezzo-piano_arco-normal.mp3\n",
      "Get cello_Gs5_1_forte_arco-normal.mp3\n",
      "Get cello_Gs3_025_fortissimo_arco-normal.mp3\n",
      "Get cello_Gs4_05_forte_arco-normal.mp3\n",
      "Get cello_Gs4_025_fortissimo_arco-normal.mp3\n",
      "Get cello_A3_15_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A3_1_mezzo-piano_arco-normal.mp3\n",
      "Get cello_Gs3_15_fortissimo_arco-normal.mp3\n",
      "Get cello_Gs5_05_pianissimo_arco-normal.mp3\n",
      "Get cello_A4_025_mezzo-piano_arco-normal.mp3\n",
      "Get cello_Gs4_025_mezzo-forte_arco-col-legno-battuto.mp3\n",
      "Get cello_A2_05_fortissimo_arco-normal.mp3\n",
      "Get cello_Gs3_025_forte_arco-normal.mp3\n",
      "Get cello_Gs4_1_fortissimo_arco-normal.mp3\n",
      "Get cello_Gs5_1_mezzo-piano_arco-normal.mp3\n",
      "Get cello_Gs3_05_forte_arco-normal.mp3\n",
      "Get cello_Gs5_15_pianissimo_arco-normal.mp3\n",
      "Get cello_Gs5_15_fortissimo_arco-normal.mp3\n",
      "Get cello_Gs3_15_piano_arco-normal.mp3\n",
      "Get cello_A3_1_fortissimo_arco-normal.mp3\n",
      "Get cello_Gs3_15_pianissimo_arco-normal.mp3\n",
      "Get cello_Gs5_025_forte_arco-normal.mp3\n",
      "Get cello_Gs3_05_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A3_1_mezzo-piano_arco-minor-trill.mp3\n",
      "Get cello_A4_1_mezzo-forte_arco-harmonic.mp3\n",
      "Get cello_A4_025_pianissimo_arco-normal.mp3\n",
      "Get cello_A2_025_mezzo-piano_arco-normal.mp3\n",
      "Get cello_Gs4_1_forte_arco-normal.mp3\n",
      "Get cello_Gs3_025_pianissimo_arco-normal.mp3\n",
      "Get cello_Gs5_15_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A3_05_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A3_025_fortissimo_arco-normal.mp3\n",
      "Get cello_Gs5_1_mezzo-forte_arco-harmonic.mp3\n",
      "Get cello_Gs5_05_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A4_025_fortissimo_arco-normal.mp3\n",
      "Get cello_Gs5_025_fortissimo_arco-normal.mp3\n",
      "Get cello_A4_1_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A4_1_forte_arco-normal.mp3\n",
      "Get cello_Gs4_05_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A4_025_mezzo-forte_arco-col-legno-battuto.mp3\n",
      "Get cello_A4_1_mezzo-piano_arco-minor-trill.mp3\n",
      "Get cello_Gs4_1_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A4_025_forte_arco-normal.mp3\n",
      "Get cello_Gs5_025_pianissimo_arco-normal.mp3\n",
      "Get cello_A2_05_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A4_15_mezzo-piano_arco-normal.mp3\n",
      "Get cello_Gs4_025_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A4_05_forte_arco-normal.mp3\n",
      "Get cello_A2_15_forte_arco-normal.mp3\n",
      "Get cello_Gs3_15_forte_arco-normal.mp3\n",
      "Get cello_Gs4_1_pianissimo_arco-normal.mp3\n",
      "Get cello_Gs4_15_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A3_025_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A3_15_forte_arco-normal.mp3\n",
      "Get cello_A2_15_pianissimo_arco-normal.mp3\n",
      "Get cello_Gs5_1_fortissimo_arco-normal.mp3\n",
      "Get cello_A2_025_pianissimo_arco-normal.mp3\n",
      "Get cello_A2_1_pianissimo_arco-normal.mp3\n",
      "Get cello_Gs4_05_fortissimo_arco-normal.mp3\n",
      "Get cello_A4_1_fortissimo_arco-normal.mp3\n",
      "Get cello_Gs3_05_pianissimo_arco-normal.mp3\n",
      "Get cello_A3_025_mezzo-forte_arco-col-legno-battuto.mp3\n",
      "Get cello_Gs4_025_pianissimo_arco-normal.mp3\n",
      "Get cello_A2_1_mezzo-piano_non-vibrato.mp3\n",
      "Get cello_A4_1_mezzo-piano_molto-vibrato.mp3\n",
      "Get cello_Gs4_15_forte_arco-normal.mp3\n",
      "Get cello_Gs3_1_pianissimo_arco-normal.mp3\n",
      "Get cello_Gs5_1_pianissimo_arco-normal.mp3\n",
      "Get cello_A4_15_forte_arco-normal.mp3\n",
      "Get cello_A2_025_forte_arco-normal.mp3\n",
      "Get cello_A2_025_fortissimo_arco-normal.mp3\n",
      "Get cello_A2_15_piano_arco-normal.mp3\n",
      "Get cello_A2_025_mezzo-forte_arco-col-legno-battuto.mp3\n",
      "Get cello_A2_05_forte_arco-normal.mp3\n",
      "Get cello_A4_1_pianissimo_arco-normal.mp3\n",
      "Get cello_Gs4_15_fortissimo_arco-normal.mp3\n",
      "Get cello_A3_1_forte_arco-normal.mp3\n",
      "Get cello_Gs3_05_fortissimo_arco-normal.mp3\n",
      "Get cello_Gs2_025_pianissimo_arco-normal.mp3\n",
      "Get cello_A3_025_forte_arco-normal.mp3\n",
      "Get cello_A2_1_mezzo-piano_arco-normal.mp3\n",
      "Get cello_A4_05_pianissimo_arco-normal.mp3\n",
      "Found 600 audio files in ./audio/london_phill_dataset_multi/\n"
     ]
    }
   ],
   "source": [
    "# Get Audio Files and Generate Labels\n",
    "files = []\n",
    "labels =[]\n",
    "classes=['flute','sax','oboe', 'cello','trumpet','viola']\n",
    "for root, dirnames, filenames in os.walk(path):\n",
    "    for i, filename in enumerate(fnmatch.filter(filenames, '*.mp3')):\n",
    "        files.append(os.path.join(root, filename))\n",
    "        print (\"Get %s\"%(filename))\n",
    "        for name in classes:\n",
    "            if fnmatch.fnmatchcase(filename, '*'+name+'*'):\n",
    "                labels.append(name)\n",
    "                break\n",
    "        else:\n",
    "            labels.append('other')\n",
    "print(\"Found %d audio files in %s\"%(len(files),path))"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Encode Labels"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "6 classes: cello, flute, oboe, sax, trumpet, viola\n"
     ]
    }
   ],
   "source": [
    "# Encode Labels\n",
    "labelencoder = LabelEncoder()\n",
    "labelencoder.fit(labels)\n",
    "print(len(labelencoder.classes_), \"classes:\", \", \".join(list(labelencoder.classes_)))\n",
    "classes_int = labelencoder.transform(labels)\n",
    "#OneHotEncoding\n",
    "encoder=OneHotEncoder(sparse=False, categories=\"auto\")\n",
    "onehot_labels=encoder.fit_transform(classes_int.reshape(len(classes_int),1))"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Create Train and Test Sets"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 6,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Create Train and Test Sets\n",
    "splitter = StratifiedShuffleSplit(n_splits=1, test_size=testset_size, random_state=0)\n",
    "splits = splitter.split(files, classes_int)\n",
    "files_arr=np.array(files)\n",
    "labels_arr=np.array(onehot_labels)\n",
    "\n",
    "for train_index, test_index in splits:\n",
    "    train_set_files = files_arr[train_index]\n",
    "    test_set_files = files_arr[test_index]\n",
    "    train_labels = labels_arr[train_index]\n",
    "    test_labels = labels_arr[test_index]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Dataset Class\n",
    "class Dataset(Dataset):\n",
    "    'An abstract class representing a Dataset.'\n",
    "    def __init__(self, files, labels):\n",
    "        self.labels = labels\n",
    "        self.files = files\n",
    "\n",
    "    def __len__(self):\n",
    "        return len(self.files)\n",
    "\n",
    "    def __getitem__(self, index):\n",
    "        x, sr = librosa.load(self.files[index], sr=fs) # Load Audio File\n",
    "        x, ind = librosa.effects.trim(x,top_db=60) #Trim\n",
    "        x = normalize(x) # Normalize\n",
    "        x = x.reshape(1,-1) # Reshape for TorchAudio PadTrim\n",
    "        duration_in_samples = librosa.time_to_samples(duration, sr=fs) # Calculate the number os samples for a duration in Time\n",
    "        X_torch = torch.from_numpy(x).to(device) \n",
    "        X_pad = transforms.PadTrim(max_len=int(duration_in_samples), channels_first=True)(X_torch) # Trim Array to defined duration\n",
    "        window = torch.hann_window(n_fft).to(device) # Hann Window\n",
    "        X_fft = torch.stft(X_pad, hop_length = hop_length, n_fft=n_fft, window=window) # PyTorch STFT\n",
    "        x_fft = X_fft[:,:,:,1].squeeze().cpu().numpy() #Reshape for Librosa Amplitude_To_dB\n",
    "        x_spec=librosa.amplitude_to_db(np.abs(x_fft), np.min) #Amplitude to dB\n",
    "        scaler = StandardScaler() #Scikit Learn Standard Scaler\n",
    "        x_spec = scaler.fit_transform(x_spec) #Apply Scaler\n",
    "        x_spec = x_spec.reshape(1,x_spec.shape[0],x_spec.shape[1]) #Reshape for PyTorch\n",
    "        X_torch = torch.from_numpy(x_spec) \n",
    "        y_labels = torch.tensor(self.labels[index]) #Labels Out\n",
    "        return X_torch, y_labels"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 8,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Create Sets\n",
    "train_set = Dataset(train_set_files, train_labels)\n",
    "test_set = Dataset(test_set_files, test_labels)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 9,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Data Loader.\n",
    "training_generator = DataLoader(train_set, batch_size=batch_size, shuffle=False, num_workers=0)\n",
    "validation_generator = DataLoader(test_set, batch_size=batch_size, shuffle=False, num_workers=0)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 10,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Spectogram Array Shape: (1025, 87)\n"
     ]
    },
    {
     "data": {
      "image/png": "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\n",
      "text/plain": [
       "<Figure size 1008x576 with 1 Axes>"
      ]
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "# Testing Dataset + Dataloader\n",
    "# Get a random spectogram sample and plot \n",
    "dataiter = iter(DataLoader(train_set, batch_size=batch_size, shuffle=True, num_workers=0))\n",
    "spectogram = dataiter.next()[0]\n",
    "# Plot Sample Spectogram\n",
    "plt.figure(figsize=(14,8));\n",
    "plt.title(\"Short-Time Fourier Transform Spectogram\\n\")\n",
    "librosa.display.specshow(spectogram[0].squeeze().numpy(),sr=fs,y_axis='log', x_axis='time', cmap=\"gray_r\")\n",
    "print(\"Spectogram Array Shape:\",spectogram[0].squeeze().squeeze().numpy().shape)\n",
    "plt.show();"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Aux Function to Calculate Layer Shapes\n",
    "\n",
    "Conv2d: $H_{out} = \\left\\lfloor\\frac{H_{in}  + 2 \\times \\text{padding}[0] - \\text{dilation}[0]\n",
    "                        \\times (\\text{kernel}[0] - 1) - 1}{\\text{stride}[0]} + 1\\right\\rfloor$\n",
    "        $W_{out} = \\left\\lfloor\\frac{W_{in}  + 2 \\times \\text{padding}[1] - \\text{dilation}[1]\n",
    "                        \\times (\\text{kernel}[1] - 1) - 1}{\\text{stride}[1]} + 1\\right\\rfloor$"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 11,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Aux Function to Calculate Layer Shapes\n",
    "# https://discuss.pytorch.org/t/utility-function-for-calculating-the-shape-of-a-conv-output/11173/5\n",
    "def conv_shape(h_w, kernel_size=3, stride=1, pad=0, dilation=1):\n",
    "    from math import floor\n",
    "    if type(kernel_size) is not tuple:\n",
    "        kernel_size = (kernel_size, kernel_size)\n",
    "    h = floor( ((h_w[0] + (2 * pad) - ( dilation * (kernel_size[0] - 1) ) - 1 )/ stride) + 1)\n",
    "    w = floor( ((h_w[1] + (2 * pad) - ( dilation * (kernel_size[1] - 1) ) - 1 )/ stride) + 1)\n",
    "    return h, w    "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 12,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "(85, 1023)\n",
      "(42, 511)\n",
      "(40, 509)\n",
      "(20, 254)\n",
      "81280\n"
     ]
    }
   ],
   "source": [
    "# Model Layers Shape Calculation\n",
    "# Input Shape\n",
    "input_shape=(87, 1025)\n",
    "# Conv1 Input: 1 Channel, Output 16 Channels, Kernel: 3x3, Stride: 1x1, Dilatation=1x1, Padding=0\n",
    "conv1_out_shape=conv_shape(input_shape)\n",
    "print(conv1_out_shape)\n",
    "pooling1_out_shape=conv_shape(conv1_out_shape, kernel_size=2, stride=2)\n",
    "print(pooling1_out_shape)\n",
    "# Conv1 Input: 16 Channel, Output 16 Channels, Kernel: 3x3, Stride: 1x1, Dilatation=1x1, Padding=0\n",
    "conv2_out_shape=conv_shape(pooling1_out_shape)\n",
    "print(conv2_out_shape)\n",
    "pooling2_out_shape=conv_shape(conv2_out_shape, kernel_size=2, stride=2)\n",
    "print(pooling2_out_shape)\n",
    "# Flatten: 16 channles * Pooling2_H * Pooling2_W\n",
    "print(16*pooling2_out_shape[0]*pooling2_out_shape[1])\n",
    "# Fully Conected 81280 In and 16 Out\n",
    "# Fully Connecte 16 In and 6 Out\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Define a CNN Model"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 13,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Model Architecture\n",
    "class modelCNN(torch.nn.Module):\n",
    "    def __init__(self):\n",
    "        super(modelCNN, self).__init__()\n",
    "        self.conv1 = torch.nn.Conv2d(1, 16, kernel_size=3, stride=1, padding=0)\n",
    "        self.pool1 = torch.nn.MaxPool2d(2)\n",
    "        self.dropout1 = torch.nn.Dropout(p=0.4)\n",
    "        self.conv2 = torch.nn.Conv2d(16, 16, kernel_size=3, stride=1, padding=0)\n",
    "        self.pool2 = torch.nn.MaxPool2d(2)\n",
    "        self.dropout2 = torch.nn.Dropout(p=0.4)\n",
    "        self.fc1 = torch.nn.Linear(16*254*20, 16)\n",
    "        self.fc2 = torch.nn.Linear(16, 6)\n",
    "        \n",
    "    def forward(self, x):\n",
    "        x = self.conv1(x)\n",
    "        x = self.pool1(x)\n",
    "        x = self.dropout1(x)\n",
    "        x = self.conv2(x)\n",
    "        x = self.pool2(x)\n",
    "        x = self.dropout2(x)\n",
    "        x = x.view(x.size()[0], -1)\n",
    "        x = torch.sigmoid(self.fc1(x))\n",
    "        x = F.softmax(self.fc2(x), dim=-1)\n",
    "        return x"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 14,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Weights Initialization Function\n",
    "def weights_init(m):\n",
    "    if isinstance(m, nn.Conv2d):\n",
    "        torch.nn.init.xavier_uniform_(m.weight.data)\n",
    "        torch.nn.init.zeros_(m.bias.data)\n",
    "    if isinstance(m, nn.Linear):\n",
    "        torch.nn.init.xavier_uniform_(m.weight.data)\n",
    "        torch.nn.init.zeros_(m.bias.data)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 15,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "modelCNN(\n",
       "  (conv1): Conv2d(1, 16, kernel_size=(3, 3), stride=(1, 1))\n",
       "  (pool1): MaxPool2d(kernel_size=2, stride=2, padding=0, dilation=1, ceil_mode=False)\n",
       "  (dropout1): Dropout(p=0.4)\n",
       "  (conv2): Conv2d(16, 16, kernel_size=(3, 3), stride=(1, 1))\n",
       "  (pool2): MaxPool2d(kernel_size=2, stride=2, padding=0, dilation=1, ceil_mode=False)\n",
       "  (dropout2): Dropout(p=0.4)\n",
       "  (fc1): Linear(in_features=81280, out_features=16, bias=True)\n",
       "  (fc2): Linear(in_features=16, out_features=6, bias=True)\n",
       ")"
      ]
     },
     "execution_count": 15,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "# Create Model and Initialize Weights\n",
    "net = modelCNN()\n",
    "net.apply(weights_init)\n",
    "net.to(device)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 16,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Number of Trainable Parameters: 1303078\n"
     ]
    }
   ],
   "source": [
    "# Display Number of Trainable Parameters\n",
    "pytorch_total_params = sum(p.numel() for p in net.parameters() if p.requires_grad)\n",
    "print(\"Number of Trainable Parameters:\",pytorch_total_params)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Aux Functions to Smooth Loss and Monitor Training Progress"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 17,
   "metadata": {},
   "outputs": [],
   "source": [
    "# https://colab.research.google.com/drive/11v_mM2ImWdKDs_4qkoB9TdsQiPgVeeo2#scrollTo=NQgIwI5WC-07        \n",
    "class ProgressMonitor(object):\n",
    "    \"\"\"\n",
    "    Custom IPython progress bar\n",
    "    \"\"\"\n",
    "    \n",
    "    tmpl_train =\"\"\"\n",
    "        <p> Train Epoch: {epoch} / {num_epochs} <br>\n",
    "        Step: {value} / {length} - Train Loss: {loss:0.4f} / Accuracy: {accuracy:0.4f}   </p>\n",
    "        <progress value='{value}' max='{length}', style='width: 100%'>{value}</progress>\n",
    "        <br>\"\"\"\n",
    "    \n",
    "    tmpl_test= \"\"\"\n",
    "        <p>Test Epoch: {epoch} / {num_epochs} <br>\n",
    "        Step: {value} / {length} - Test Loss: {loss:0.4f}  /  Accuracy: {accuracy:0.4f} </p>\n",
    "        <progress value='{value}' max='{length}', style='width: 100%'>{value}</progress>\n",
    "        <br>\"\"\"\n",
    "\n",
    "    def __init__(self, length, mode):\n",
    "        self.length = length\n",
    "        self.count = 0\n",
    "        self.mode = mode\n",
    "        self.display = display(self.html(0, 0, 0, 0, 0, mode), display_id=True)   \n",
    "        \n",
    "    def html(self, count, epoch, num_epochs, loss, accuracy, mode=\"train\"):\n",
    "        if mode==\"train\":\n",
    "            return HTML(self.tmpl_train.format(length=self.length, value=count, epoch=epoch, num_epochs=num_epochs, loss=loss, accuracy=accuracy))\n",
    "        else:\n",
    "            return HTML(self.tmpl_test.format(length=self.length, value=count, epoch=epoch, num_epochs=num_epochs, loss=loss, accuracy=accuracy))\n",
    "        \n",
    "    def update(self, count, epoch, num_epochs, loss, accuracy, mode=\"train\"):\n",
    "        self.count += count\n",
    "        self.display.update(self.html(self.count, epoch, num_epochs, loss, accuracy, mode))\n",
    "\n",
    "# https://colab.research.google.com/drive/1gJAAN3UI9005ecVmxPun5ZLCGu4YBtLo#scrollTo=ZvoPaJvs7Eem\n",
    "class AverageBase(object):\n",
    "    \n",
    "    def __init__(self, value=0):\n",
    "        self.value = float(value) if value is not None else None\n",
    "       \n",
    "    def __str__(self):\n",
    "        return str(round(self.value, 4))\n",
    "    \n",
    "    def __repr__(self):\n",
    "        return self.value\n",
    "    \n",
    "    def __format__(self, fmt):\n",
    "        return self.value.__format__(fmt)\n",
    "    \n",
    "    def __float__(self):\n",
    "        return self.value\n",
    "    \n",
    "\n",
    "class RunningAverage(AverageBase):\n",
    "    \"\"\"\n",
    "    Keeps track of a cumulative moving average (CMA).\n",
    "    \"\"\"\n",
    "    \n",
    "    def __init__(self, value=0, count=0):\n",
    "        super(RunningAverage, self).__init__(value)\n",
    "        self.count = count\n",
    "        \n",
    "    def update(self, value):\n",
    "        self.value = (self.value * self.count + float(value))\n",
    "        self.count += 1\n",
    "        self.value /= self.count\n",
    "        return self.value\n",
    "\n",
    "\n",
    "class MovingAverage(AverageBase):\n",
    "    \"\"\"\n",
    "    An exponentially decaying moving average (EMA).\n",
    "    \"\"\"\n",
    "    \n",
    "    def __init__(self, alpha=0.99):\n",
    "        super(MovingAverage, self).__init__(None)\n",
    "        self.alpha = alpha\n",
    "        \n",
    "    def update(self, value):\n",
    "        if self.value is None:\n",
    "            self.value = float(value)\n",
    "        else:\n",
    "            self.value = self.alpha * self.value + (1 - self.alpha) * float(value)\n",
    "        return self.value"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Define Loss Function and Optimizer"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 18,
   "metadata": {},
   "outputs": [],
   "source": [
    "class categorical_cross_entropy(nn.Module):\n",
    "    ''' Categorical Cross Entropy similar to Keras/TensorFlow\n",
    "        \"Categorical crossentropy between an output tensor and a target tensor\" - https://www.tensorflow.org/api_docs/python/tf/keras/backend/categorical_crossentropy\n",
    "        https://github.com/tensorflow/tensorflow/blob/r1.13/tensorflow/python/keras/backend.py\n",
    "        target: A tensor of the same shape as `inputX`.\n",
    "        inputX: A tensor resulting from a softmax\n",
    "    '''\n",
    "    def __init__(self):\n",
    "        super(categorical_cross_entropy, self).__init__()\n",
    "\n",
    "    def forward(self, inputX, target):\n",
    "        eps=1e-10\n",
    "        tmp = inputX.clone()\n",
    "        tmp /= torch.sum(tmp)\n",
    "        torch.clamp_(tmp, min=eps, max = 1-eps)\n",
    "        return torch.mean(-torch.sum(target * torch.log(tmp.double()), dim=-1), dim=-1)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 19,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Loss Function\n",
    "criterion = categorical_cross_entropy()\n",
    "\n",
    "# Optimizer\n",
    "optimizer = optim.SGD(net.parameters(), lr=lr)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Aux Functions to Save and Load Checkpoints"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 20,
   "metadata": {},
   "outputs": [],
   "source": [
    "def save_checkpoint(optimizer, criterion, model, epoch, filename):\n",
    "    checkpoint_dict = {\n",
    "        'optimizer': optimizer.state_dict(),\n",
    "        'model': model.state_dict(),\n",
    "        'epoch': epoch,\n",
    "        'criterion': criterion.state_dict()\n",
    "    }\n",
    "    torch.save(checkpoint_dict, filename)\n",
    "\n",
    "\n",
    "def load_checkpoint(optimizer, criterion, model, filename):\n",
    "    checkpoint_dict = torch.load(filename)\n",
    "    epoch = checkpoint_dict['epoch']\n",
    "    model.load_state_dict(checkpoint_dict['model'])\n",
    "    criterion.load_state_dict(checkpoint_dict['criterion'])\n",
    "    if optimizer is not None:\n",
    "        optimizer.load_state_dict(checkpoint_dict['optimizer'])\n",
    "    return epoch"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# Define a Train Function"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 21,
   "metadata": {},
   "outputs": [],
   "source": [
    "def train(model, epoch, num_epochs, monitoring=True):\n",
    "    \n",
    "    if monitoring:\n",
    "         #Create a Progress Bar \n",
    "        if inColab:\n",
    "            try:\n",
    "                # create a progress bar\n",
    "                with grid.output_to(0,0):\n",
    "                    progress = ProgressMonitor(length=len(train_set), mode=\"train\")\n",
    "            except:\n",
    "                pass\n",
    "        else:\n",
    "            progress = ProgressMonitor(length=len(train_set), mode=\"train\")\n",
    "        \n",
    "    \n",
    "    # Initialize Metrics\n",
    "    train_loss = MovingAverage()\n",
    "    train_acc = MovingAverage()\n",
    "    \n",
    "    # Train Stage\n",
    "    model.train()\n",
    "    \n",
    "    # keep track of X predictions amd metrics\n",
    "    x_pred = []\n",
    "\n",
    "    for i, (batch, targets) in enumerate(training_generator):\n",
    "        # Move the training data to the GPU\n",
    "        batch = batch.to(device)\n",
    "        targets = targets.to(device)\n",
    "\n",
    "        # clear previous gradient computation\n",
    "        optimizer.zero_grad()\n",
    "\n",
    "        # forward propagation\n",
    "        predictions = model(batch)\n",
    "\n",
    "        # calculate the loss\n",
    "        loss = criterion(predictions, targets)\n",
    "        #loss = cross_entropy(predictions, targets)\n",
    "\n",
    "        # backpropagate to compute gradients\n",
    "        loss.backward()\n",
    "\n",
    "        # update model weights\n",
    "        optimizer.step()\n",
    "\n",
    "        # update average loss\n",
    "        train_loss.update(loss)\n",
    "            \n",
    "        # save X predictions\n",
    "        x_pred.extend(predictions.argmax(dim=-1).cpu().numpy())\n",
    "        \n",
    "        # calculate accuracy\n",
    "        x_pred_torch = torch.tensor(x_pred, dtype=torch.int64)\n",
    "        accuracy = torch.mean((x_pred_torch == torch.tensor(np.argmax(train_set.labels[:len(x_pred)],axis=1), dtype=torch.int64)).float())\n",
    "        \n",
    "        # update average accuracy\n",
    "        train_acc.update(accuracy)\n",
    "            \n",
    "        # Update Progress Bar\n",
    "        if monitoring:\n",
    "                progress.update(batch.shape[0], epoch, num_epochs, train_loss, train_acc, mode=\"train\")\n",
    "                \n",
    "    #TensorBoard\n",
    "    if inColab:\n",
    "        try:\n",
    "            tbc.save_value('Loss', 'train_loss', epoch, train_loss.value)\n",
    "            tbc.save_value('Accuracy', 'train_acc', epoch, train_acc.value)\n",
    "        except:\n",
    "            pass\n",
    "\n",
    "    # Save a checkpoint\n",
    "    checkpoint_filename = 'checkpoints/basicInstrumetClassif-{:03d}.pkl'.format(epoch)\n",
    "    save_checkpoint(optimizer, criterion, model, epoch, checkpoint_filename)\n",
    "    return train_loss.value, train_acc.value , x_pred"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Define a Test Function"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 22,
   "metadata": {},
   "outputs": [],
   "source": [
    "def test(model, epoch, num_epochs, monitoring=True):\n",
    "    \n",
    "    if monitoring:\n",
    "        #Create a Progress Bar\n",
    "        if inColab:\n",
    "            try:\n",
    "                with grid.output_to(0,0):\n",
    "                    progress = ProgressMonitor(length=len(test_set), mode=\"test\")\n",
    "            except:\n",
    "                pass\n",
    "        else:\n",
    "            progress = ProgressMonitor(length=len(test_set), mode=\"test\")\n",
    "    \n",
    "    \n",
    "    # validation phase\n",
    "    model.eval()\n",
    "    \n",
    "    #Initialize Metrics\n",
    "    valid_loss = RunningAverage()\n",
    "    valid_acc = RunningAverage()\n",
    "\n",
    "    # keep track of predictions\n",
    "    y_pred = []\n",
    "    \n",
    "    with torch.no_grad():\n",
    "        for batch, targets in validation_generator:\n",
    "\n",
    "            # Move the training batch to the GPU\n",
    "            batch = batch.to(device)\n",
    "            targets = targets.to(device)\n",
    "\n",
    "            # forward propagation\n",
    "            predictions = model(batch)\n",
    "\n",
    "            # calculate the loss\n",
    "            loss = criterion(predictions, targets)\n",
    "\n",
    "            # update running loss value\n",
    "            valid_loss.update(loss)\n",
    "\n",
    "            # save predictions\n",
    "            y_pred.extend(predictions.argmax(dim=1).cpu().numpy())\n",
    "\n",
    "            # Validation Accuracy\n",
    "            y_pred_torch = torch.tensor(y_pred, dtype=torch.int64)\n",
    "            accuracy = torch.mean((y_pred_torch == torch.tensor(np.argmax(test_set.labels[:len(y_pred)],axis=1), dtype=torch.int64)).float())\n",
    "            valid_acc.update(accuracy)\n",
    "\n",
    "            # Update Progress Bar\n",
    "            if monitoring:\n",
    "                    progress.update(batch.shape[0], epoch, num_epochs, valid_loss, valid_acc, mode=\"test\")\n",
    "                    \n",
    "    #TensorBoard\n",
    "    if inColab:\n",
    "        try:\n",
    "            tbc.save_value('Loss', 'valid_loss', epoch, valid_loss.value)\n",
    "            tbc.save_value('Accuracy', 'valid_acc', epoch, valid_acc.value)\n",
    "        except:\n",
    "            pass\n",
    "        \n",
    "    return valid_loss.value, valid_acc.value, y_pred\n",
    "    "
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Define an Experiment Function"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 23,
   "metadata": {},
   "outputs": [],
   "source": [
    "def experiment(model, num_epochs = num_epochs, first_epoch = 1, monitoring=True):\n",
    "    \n",
    "    #Initialze Metrics\n",
    "    train_losses = []\n",
    "    train_accuracies = []\n",
    "    valid_losses = []\n",
    "    valid_accuracies = []\n",
    "    \n",
    "    if inColab:\n",
    "        global tbc\n",
    "        tbc = TensorBoardColab()\n",
    "        if monitoring:\n",
    "            # create a 1x1 grid to display the loss and progress\n",
    "            global grid\n",
    "            grid = widgets.Grid(3,1)\n",
    "    \n",
    "    for epoch in range(first_epoch, first_epoch + num_epochs):\n",
    "        #Train Model\n",
    "        train_loss,train_acc,train_predictions=train(model, epoch, num_epochs, monitoring)\n",
    "        #Save Test Losses and Accuracies\n",
    "        train_losses.append(train_loss)\n",
    "        train_accuracies.append(train_acc)\n",
    "        #Test Model\n",
    "        valid_loss,valid_acc, valid_predictions = test(model, epoch, num_epochs, monitoring)\n",
    "        #Save Test Losses and Accuracies\n",
    "        valid_losses.append(valid_loss)\n",
    "        valid_accuracies.append(valid_acc)\n",
    "        \n",
    "        if monitoring:\n",
    "            if inColab:\n",
    "                try:\n",
    "                    # Plot loss\n",
    "                    with grid.output_to(1, 0):\n",
    "                        grid.clear_cell()\n",
    "                        plt.figure(figsize=(10,6))\n",
    "                        epochs = range(first_epoch, epoch + 1)\n",
    "                        plt.plot(epochs, train_losses, '-o', label='Training')\n",
    "                        plt.plot(epochs, valid_losses, '-o', label='Validation')\n",
    "                        plt.legend()\n",
    "                        plt.title('Learning curves')\n",
    "                        plt.xlabel('Epoch')\n",
    "                        plt.ylabel('Loss')\n",
    "                        plt.xticks(epochs)\n",
    "                        plt.show()\n",
    "\n",
    "                    # Plot Accuracy\n",
    "                    with grid.output_to(2, 0):\n",
    "                        grid.clear_cell()\n",
    "                        plt.figure(figsize=(10,6))\n",
    "                        epochs = range(first_epoch, epoch + 1)\n",
    "                        plt.plot(epochs, train_accuracies, '-o', label='Training')\n",
    "                        plt.plot(epochs, valid_accuracies, '-o', label='Validation')\n",
    "                        plt.legend()\n",
    "                        plt.title('Learning curves')\n",
    "                        plt.xlabel('Epoch')\n",
    "                        plt.ylabel('Accuracy')\n",
    "                        plt.xticks(epochs)\n",
    "                        plt.show()\n",
    "                except:\n",
    "                    pass\n",
    "                \n",
    "    return {\"train_loss\": train_losses, \"train_acc\": train_accuracies, \"valid_loss\" : valid_losses, \n",
    "            \"valid_acc\" : valid_accuracies, \"predictions\" :valid_predictions }"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Run Experiment"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 24,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 1 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.8150 / Accuracy: 0.6163   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 1 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.6791  /  Accuracy: 0.8387 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 2 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.4007 / Accuracy: 0.9102   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 2 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.4356  /  Accuracy: 0.9309 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 3 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.2218 / Accuracy: 0.9926   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 3 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.2575  /  Accuracy: 0.9586 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 4 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.1294 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 4 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.1575  /  Accuracy: 1.0000 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 5 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.0889 / Accuracy: 0.9973   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 5 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.1259  /  Accuracy: 1.0000 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 6 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.0640 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 6 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.1051  /  Accuracy: 1.0000 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 7 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.0530 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 7 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.1053  /  Accuracy: 0.9950 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 8 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.0450 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 8 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.0891  /  Accuracy: 1.0000 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 9 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.0388 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 9 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.0827  /  Accuracy: 0.9976 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 10 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.0343 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 10 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.0757  /  Accuracy: 0.9927 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 11 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.0316 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 11 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.0684  /  Accuracy: 1.0000 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 12 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.0274 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 12 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.0611  /  Accuracy: 1.0000 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 13 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.0248 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 13 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.0596  /  Accuracy: 1.0000 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 14 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.0226 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 14 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.0548  /  Accuracy: 1.0000 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 15 / 15 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.0221 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 15 / 15 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.0474  /  Accuracy: 1.0000 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "# Run Experiment\n",
    "hist = experiment(net, num_epochs=num_epochs, monitoring=True)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Evaluate Model"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 25,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "image/png": "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d45zrqNz7pHSfc85554r/bzTOXexc66Xc66nc+41X+Y5WWntEsnacuCkl2wQERHxuxUz4KmeMDUenupJ2Np3T+t048aN48SX6DIyMhg3blytjm/VqhVvvfXWKV//xIJs1qxZxMfHn/L5gl3gR6sHsbTkBPYdLmDz3sOBjiIiIlK9FTPggzshdzvgIHc7Uf/+jWf/KRo9ejQffvghx44dA2DLli3s3LmTc889t2xesJSUFHr16sX7779f6fgtW7bQs2dPAPLz8xk7diyDBw/muuuuIz//h3U3f/azn5GWlkaPHj144IEHAHjmmWfYuXMn6enppKenA5CcnMzevZ6HaE8++SQ9e/akZ8+ePP3002XX69atG7feeis9evTg4osvrnCdKv/YVqxg0KBB9O7dm6uvvpoDBw6UXb979+707t27bALbefPm0bdvX/r27Uu/fv3qdOJd0NJJXvVPTgA848g6NA2eV6tFROQsM3sKfL+y+vbsRVB8rMIuK8qH92+HxS9XfUyLXjDi0arb8CzEPWDAAD766COuuuoqMjIyuO666zAzoqKiePfdd2nUqBF79+5l0KBBXHnllXimFa3sL3/5Cw0aNGDBggVs3ryZlJSUsrZHHnmExMREiouLGT58OCtWrODOO+/kySefJDMzkyZNmlQ41+LFi5k+fTpff/01zjkGDhzI0KFDSUhIYMOGDbz55pu88MILjBkzhrfffpvx48dX+xt/+tOfMm3aNIYOHcr999/Pgw8+yNNPP82jjz7K5s2biYyMLHtM+sQTTzBt2jSGDBlCXl4eUVFR1Z73VOgOmRcdm8aQ0CCcRVs0jkxERILYCcVYjftrqfxjy/KPK51z/Pa3v6V3795ceOGF7Nixg127dlV7nvnz55cVRr1796Z3795lbTNmzCAlJYV+/fqxevXqGhcO//zzz7n66qtp2LAhMTExjBo1is8++wyA9u3b07dvXwBSU1PZsmVLtefJzc0lNzeXoUOHAnDTTTcxf/78sow33HADr732WtmKAEOGDGHy5Mk888wz5OTk1PlKAbpD5oWZkdoukaytetNSREQCyMudLMAzdix3e+X9cW3g5krzrdfayJEjmTx5MkuWLCE/P7/sztbrr7/Onj17WLx4MeHh4SQnJ3P06FGv56rq7tnmzZt54oknWLRoEQkJCUycOLHG83gb1x0ZGVn2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\n",
      "text/plain": [
       "<Figure size 720x432 with 1 Axes>"
      ]
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    },
    {
     "data": {
      "image/png": "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v2bIkCE89dRTvP7660ydOrXJXN/85je5/vrrKSgo4IorrmDhwoWce+65XH755dx6662cf/75VFVVUV9fz3PPPcdf//pXli1bRm5uLrt37271c7/22musWbOGvn37UlNTw1/+8hcKCwspKSnhtNNO47zzzuP111/npz/9Ka+++ir9+vXj/fffp0+fPpx22mksXLiQ8847j0cffZRLL730iN9jZ1DPWjuESsKkpxmj+ucnO4qIiHRRjQu11tZ31NixYzn55JMPLj/22GNMnTqVqVOnsn79etatW3fEPrm5uZx77rkAFBUVHezdauyiiy46os0rr7zC7NmzAZgyZQrHH990kbl48WJmzJjBlClTWLp0KW+99RZ79uxh586dnH/++UDkPmV5eXn87W9/44tf/CK5uZE7MfTr16/Vz3322WfTt29fIFJU3njjjUyePJmzzz6bzZs3s3PnTv7+979z2WWXHTxew89rrrnm4LDwQw89xNVXX93q+YKgnrV2CJWEGdkvj6wM1boiItK02B6wpu7bddodf2fr3soj9hvWJ5fHv3JqwvPk5x/qYAiFQvzyl79k2bJl9OnThyuvvLLJW0tkZWUdfJ+enn5wSLCx7OzsI9o0DGe2pKKiguuuu46XX36ZCRMmcPPNNx/M0dQMSndvcn1GRsbB6/Aaf47Yz/3www+zb98+Vq1aRUZGBsOHD6eqqqrZ455xxhlcd911LFmyhMzMTI499thWP1MQVG20Q6g0rCcXiIhIh9xwzgRyMw8fUsvNTOeGcyYEfu6G4rFXr15s376dRYsWJfwcp59+Ok888QQAa9eubbLnrrKykrS0NPr3709ZWRlPPfUUAH379mXAgAE899xzQKQAq6io4Oyzz+aBBx6gsjJS5DYMg44aNYqVK1cC8OSTTzabad++fQwaNIiMjAxefPFFtm6NXB/48Y9/nHnz5h08Xuzw6pVXXsnnPve5pPWqgYq1NqutdzbtLNczQUVEpEMuPGkYP7noBIb1ycWI9Kj95KITOjQbNF4nnngiEydOZNKkSXz5y1/mtNNOS/g5vv71r7N161YmT57Mz3/+cyZNmkTv3r3///buPTyq+s7j+PtbiCbc71bABbaL4hImVxLkEqHhpmujoBgoikDRLSpY2dWKrZV9XJ62cossldZSQJ+lQKwilWq8LUh9LBaCEC4W7JYoJAhR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\n",
      "text/plain": [
       "<Figure size 720x432 with 1 Axes>"
      ]
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "epochs = range(1, len(hist[\"train_loss\"]) + 1)\n",
    "\n",
    "plt.figure(figsize=(10,6))\n",
    "plt.plot(epochs, hist[\"train_loss\"], '-o', label='Training loss')\n",
    "plt.plot(epochs, hist[\"valid_loss\"], '-o', label='Validation loss')\n",
    "plt.legend()\n",
    "plt.title('Learning curves')\n",
    "plt.xlabel('Epoch')\n",
    "plt.ylabel('Loss')\n",
    "plt.xticks(epochs)\n",
    "plt.grid()\n",
    "plt.show()\n",
    "\n",
    "plt.figure(figsize=(10,6))\n",
    "plt.plot(epochs, hist[\"train_acc\"], '-o', label='Training accuracy')\n",
    "plt.plot(epochs, hist[\"valid_acc\"], '-o', label='Validation accuracy')\n",
    "plt.legend()\n",
    "plt.title('Learning curves')\n",
    "plt.xlabel('Epoch')\n",
    "plt.ylabel('Accuracy')\n",
    "plt.xticks(epochs)\n",
    "plt.grid()\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 26,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Validation errors 0 (out of 150)\n"
     ]
    }
   ],
   "source": [
    "# Number of Validation Errors\n",
    "num_errors = torch.sum((torch.tensor(hist[\"predictions\"]) != torch.tensor(np.argmax(test_set.labels,axis=1))).float())\n",
    "print('Validation errors {} (out of {})'.format(int(num_errors), len(test_set)))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 27,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Wrongly predicted Audio Files []\n",
      "Correct Classes: []\n",
      "Predicted as: []\n"
     ]
    }
   ],
   "source": [
    "# Mistakes\n",
    "error_indicator = torch.tensor(hist[\"predictions\"]) != torch.tensor(np.argmax(test_set.labels,axis=1))\n",
    "print(\"Wrongly predicted Audio Files\", test_set.files[np.where(error_indicator)])\n",
    "print(\"Correct Classes:\", np.array(labels)[test_index[np.where(error_indicator)]])\n",
    "print(\"Predicted as:\",labelencoder.inverse_transform(np.ravel(np.array(hist[\"predictions\"])[np.where(error_indicator)])))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 28,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Back to Labels\n",
    "predictions_labels=labelencoder.inverse_transform(np.ravel(hist[\"predictions\"]));"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 29,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Recall:  [1. 1. 1. 1. 1. 1.]\n",
      "Precision:  [1. 1. 1. 1. 1. 1.]\n",
      "F1-Score:  [1. 1. 1. 1. 1. 1.]\n",
      "Accuracy: 1.00  , 150\n",
      "Number of samples: 150\n",
      "              precision    recall  f1-score   support\n",
      "\n",
      "           0       1.00      1.00      1.00        25\n",
      "           1       1.00      1.00      1.00        25\n",
      "           2       1.00      1.00      1.00        25\n",
      "           3       1.00      1.00      1.00        25\n",
      "           4       1.00      1.00      1.00        25\n",
      "           5       1.00      1.00      1.00        25\n",
      "\n",
      "   micro avg       1.00      1.00      1.00       150\n",
      "   macro avg       1.00      1.00      1.00       150\n",
      "weighted avg       1.00      1.00      1.00       150\n",
      "\n"
     ]
    }
   ],
   "source": [
    "# Recall - the ability of the classifier to find all the positive samples\n",
    "print(\"Recall: \", recall_score(classes_int[test_index], hist[\"predictions\"],average=None))\n",
    "\n",
    "# Precision - The precision is intuitively the ability of the classifier not to \n",
    "#label as positive a sample that is negative\n",
    "print(\"Precision: \", precision_score(classes_int[test_index], hist[\"predictions\"],average=None))\n",
    "\n",
    "# F1-Score - The F1 score can be interpreted as a weighted average of the precision \n",
    "#and recall\n",
    "print(\"F1-Score: \", f1_score(classes_int[test_index], hist[\"predictions\"], average=None))\n",
    "\n",
    "# Accuracy - the number of correctly classified samples\n",
    "print(\"Accuracy: %.2f  ,\" % accuracy_score(classes_int[test_index], hist[\"predictions\"] ,normalize=True), accuracy_score(classes_int[test_index], hist[\"predictions\"],normalize=False) )\n",
    "print(\"Number of samples:\",classes_int[test_index].shape[0])\n",
    "\n",
    "print(classification_report(classes_int[test_index], hist[\"predictions\"]))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 30,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Compute confusion matrix\n",
    "cnf_matrix = confusion_matrix(classes_int[test_index], hist[\"predictions\"])\n",
    "np.set_printoptions(precision=2)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 31,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Function to Plot Confusion Matrix\n",
    "# http://scikit-learn.org/stable/auto_examples/model_selection/plot_confusion_matrix.html\n",
    "def plot_confusion_matrix(cm, classes,\n",
    "                          normalize=False,\n",
    "                          title='Confusion matrix',\n",
    "                          cmap=plt.cm.Blues):\n",
    "    \"\"\"\n",
    "    This function prints and plots the confusion matrix.\n",
    "    Normalization can be applied by setting `normalize=True`.\n",
    "    \n",
    "    if normalize:\n",
    "        cm = cm.astype('float') / cm.sum(axis=1)[:, np.newaxis]\n",
    "        print(\"Normalized confusion matrix\")\n",
    "    else:\n",
    "        print('Confusion matrix, without normalization')\n",
    "    \"\"\"\n",
    "    #print(cm)\n",
    "\n",
    "    plt.imshow(cm, interpolation='nearest', cmap=cmap)\n",
    "    plt.title(title)\n",
    "    plt.colorbar()\n",
    "    tick_marks = np.arange(len(classes))\n",
    "    plt.xticks(tick_marks, classes, rotation=45)\n",
    "    plt.yticks(tick_marks, classes)\n",
    "\n",
    "    fmt = '.2f' if normalize else 'd'\n",
    "    thresh = cm.max() / 2.\n",
    "    for i, j in itertools.product(range(cm.shape[0]), range(cm.shape[1])):\n",
    "        plt.text(j, i, format(cm[i, j], fmt),\n",
    "                 horizontalalignment=\"center\",\n",
    "                 color=\"white\" if cm[i, j] > thresh else \"black\")\n",
    "\n",
    "    plt.tight_layout()\n",
    "    plt.ylabel('True label')\n",
    "    plt.xlabel('Predicted label')"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 32,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "image/png": "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\n",
      "text/plain": [
       "<Figure size 1152x864 with 2 Axes>"
      ]
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "# Plot non-normalized confusion matrix\n",
    "plt.figure(figsize=(16,12))\n",
    "plot_confusion_matrix(cnf_matrix, classes=labelencoder.classes_,\n",
    "                      title='Confusion matrix, without normalization')"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 33,
   "metadata": {},
   "outputs": [],
   "source": [
    "# Find wrong predicted samples indexes\n",
    "wrong_predictions = [i for i, (e1, e2) in enumerate(zip(classes_int[test_index], hist[\"predictions\"])) if e1 != e2]"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 34,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Correct Classes: []\n",
      "Predicted as: []\n",
      "[]\n"
     ]
    }
   ],
   "source": [
    "# Find wrong predicted audio files\n",
    "print(\"Correct Classes:\", np.array(labels)[test_index[wrong_predictions]])\n",
    "print(\"Predicted as:\", predictions_labels[wrong_predictions].T)\n",
    "print(np.array(files)[test_index[wrong_predictions]])"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Resume Training"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 35,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "basicInstrumetClassif-001.pkl  basicInstrumetClassif-009.pkl\r\n",
      "basicInstrumetClassif-002.pkl  basicInstrumetClassif-010.pkl\r\n",
      "basicInstrumetClassif-003.pkl  basicInstrumetClassif-011.pkl\r\n",
      "basicInstrumetClassif-004.pkl  basicInstrumetClassif-012.pkl\r\n",
      "basicInstrumetClassif-005.pkl  basicInstrumetClassif-013.pkl\r\n",
      "basicInstrumetClassif-006.pkl  basicInstrumetClassif-014.pkl\r\n",
      "basicInstrumetClassif-007.pkl  basicInstrumetClassif-015.pkl\r\n",
      "basicInstrumetClassif-008.pkl\r\n"
     ]
    }
   ],
   "source": [
    "!ls checkpoints"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 36,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Resuming training from epoch 2\n"
     ]
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 2 / 2 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.2157 / Accuracy: 0.9744   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 2 / 2 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.2560  /  Accuracy: 0.9763 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p> Train Epoch: 3 / 2 <br>\n",
       "        Step: 450 / 450 - Train Loss: 0.1317 / Accuracy: 1.0000   </p>\n",
       "        <progress value='450' max='450', style='width: 100%'>450</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "\n",
       "        <p>Test Epoch: 3 / 2 <br>\n",
       "        Step: 150 / 150 - Test Loss: 0.1473  /  Accuracy: 1.0000 </p>\n",
       "        <progress value='150' max='150', style='width: 100%'>150</progress>\n",
       "        <br>"
      ],
      "text/plain": [
       "<IPython.core.display.HTML object>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "epoch = load_checkpoint(optimizer, criterion, net, 'checkpoints/basicInstrumetClassif-002.pkl')\n",
    "print('Resuming training from epoch', epoch)\n",
    "hist = experiment(net, num_epochs=2, first_epoch=epoch)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.6.5"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
